import { FC, ReactElement, useCallback, useMemo, useState } from "react";
import { IDateTime } from ".";
import DateGrid from "./DateGrid";
import { SubHead } from "../Text";
import {
  Wrapper,
  CloseIcon,
  Head,
  DayItem,
  LeftIcon,
  RightIcon,
  MikeTrueIcon,
  DayContainer,
  WeekContainer,
  Content,
  ButtonGroup,
  CloseBtn,
  Operation,
  OperationBar,
} from "./styled";
import YearSelected from "./YearSelected";
import MonthSelected from "./MonthSelected";

interface IProps {
  noShadow?: boolean;
  DateTime: IDateTime;
  cancelPicker: () => void;
  toggleMonth: (num: number) => () => void;
  backToToday: () => void;
  selectDay: (day: number) => () => void;
  selectMonth: (month: number) => void;
  selectYear: (year: number) => void;
  makeTrue: () => void;
}

const TimePicker: FC<IProps> = ({
  DateTime,
  cancelPicker,
  toggleMonth,
  backToToday,
  selectDay,
  selectMonth,
  selectYear,
  makeTrue,
  noShadow,
}): ReactElement => {
  const cardType = useMemo(() => ["DAY", "MONTH", "YEAR"], []);
  const [type, setType] = useState<"DAY" | "MONTH" | "YEAR">("DAY");
  const [tempMonth, setTempMonth] = useState(DateTime.month);
  const [tempYear, setTempYear] = useState(DateTime.year);

  const handleSelectMonth = useCallback(() => {
    selectMonth(tempMonth);
    setType("DAY");
  }, [selectMonth, tempMonth]);

  const handleCloseMonth = useCallback(() => {
    setTempMonth(DateTime.month);
    setType("DAY");
  }, [DateTime.month]);

  const handleSelectYear = useCallback(() => {
    selectYear(tempYear);
    setType("DAY");
  }, [selectYear, tempYear]);

  const handleCloseYear = useCallback(() => {
    setTempYear(DateTime.year);
    setType("DAY");
  }, [DateTime.year]);

  const Operations: { [key: string]: JSX.Element } = useMemo(
    () => ({
      DAY: (
        <>
          <DayItem pointer onClick={backToToday} children='今天' />
          <DayItem pointer onClick={makeTrue} children={<MikeTrueIcon />} />
        </>
      ),
      YEAR: <DayItem pointer onClick={handleSelectYear} children='确定' />,
      MONTH: <DayItem pointer onClick={handleSelectMonth} children='确定' />,
    }),
    [backToToday, handleSelectMonth, handleSelectYear, makeTrue]
  );

  const OperationButtons: { [key: string]: JSX.Element } = useMemo(
    () => ({
      DAY: (
        <ButtonGroup>
          <DayItem onClick={toggleMonth(-1)} children={<LeftIcon />} />
          <DayItem onClick={toggleMonth(1)} children={<RightIcon />} />
        </ButtonGroup>
      ),
      YEAR: (
        <CloseBtn
          style={{ transform: "rotate(180deg)" }}
          onClose={handleCloseYear}
        />
      ),
      MONTH: <CloseBtn onClose={handleCloseMonth} />,
    }),
    [handleCloseMonth, toggleMonth, handleCloseYear]
  );

  const renderOperationItem = useCallback(
    type => (t: string, index: number) =>
      (
        <OperationBar key={index} status={type === t}>
          {Operations[t]}
          {OperationButtons[t]}
        </OperationBar>
      ),
    [OperationButtons, Operations]
  );

  const MemoOperation = useMemo(
    () => <Operation children={cardType.map(renderOperationItem(type))} />,
    [cardType, renderOperationItem, type]
  );

  const handlePickerMonth = useCallback(() => {
    if (type !== "MONTH") {
      setType("MONTH");
      setTempMonth(DateTime.month);
    } else setType("DAY");
  }, [DateTime.month, type]);

  const handlePickerYear = useCallback(() => {
    if (type !== "YEAR") {
      setType("YEAR");
      // setTempMonth(DateTime.month);
    } else setType("DAY");
  }, [type]);

  return (
    <Wrapper noShadow={noShadow}>
      <Head>
        <Title onClick={handlePickerYear} content={DateTime.year} />
        <Title onClick={handlePickerMonth} content={DateTime.month} />
        <CloseIcon onClick={cancelPicker} />
      </Head>

      <Content>
        <DayContainer>
          <WeekTitle />
          <DateGrid
            year={DateTime.year}
            month={DateTime.month}
            day={DateTime.day}
            selectDay={selectDay}
          />
        </DayContainer>
        <YearSelected
          year={tempYear}
          active={type === "YEAR"}
          selectYear={setTempYear}
        />
        <MonthSelected
          month={tempMonth}
          active={type === "MONTH"}
          selectMonth={setTempMonth}
        />
      </Content>
      {MemoOperation}
    </Wrapper>
  );
};

export default TimePicker;

const Title = ({
  content,
  onClick,
}: {
  content: string | number;
  onClick: () => void;
}) => (
  <SubHead
    onClick={onClick}
    style={{ cursor: "pointer" }}
    width='1.5rem'
    height='1.5rem'
  >
    {content}
  </SubHead>
);

const WeekTitle = () => {
  return (
    <WeekContainer>
      <SubHead>日</SubHead>
      <SubHead>一</SubHead>
      <SubHead>二</SubHead>
      <SubHead>三</SubHead>
      <SubHead>四</SubHead>
      <SubHead>五</SubHead>
      <SubHead>六</SubHead>
    </WeekContainer>
  );
};
